﻿package rd.hardcore.ui.pad 
{
	import aze.motion.eaze;
	import flash.desktop.Clipboard;
	import flash.desktop.ClipboardFormats;
	import flash.desktop.NativeDragActions;
	import flash.desktop.NativeDragManager;
	import flash.display.MovieClip;
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.events.NativeDragEvent;
	import flash.filesystem.File;
	import flash.filesystem.FileMode;
	import flash.filesystem.FileStream;
	import flash.net.URLLoader;
	import flash.net.URLRequest;
	import flash.net.URLStream;
	import flash.system.Capabilities;
	import flash.utils.ByteArray;
	import nochump.util.zip.ZipEntry;
	import nochump.util.zip.ZipFile;
	import rd.hardcore.datas.Track;
	import rd.hardcore.engine.save.SaveManager;
	import rd.hardcore.events.OutDragInEvent;
	import rd.hardcore.events.SaveManagerEvent;
	import rd.hardcore.events.TrackEvent;
	import rd.hardcore.params.GlobalParams;
	
	/**
	 * Gestionaire de drag&drop de fichier externe
	 * @TODO Gestion de la demande d'override des données présente dans le Pad
	 * @author Thibault Perret
	 */
	public class ExternalDragNDrop extends MovieClip
	{
		public var streamable : Boolean;
		
		private var sm:SaveManager;
		private var _keyId:int;
		private var _track:Track;
		
		private var overridePanel:Sprite;
		private var needOverride:Boolean = false;
		private var completePad:Boolean = false;
		
		//Comptage des fichiers déposer 1 image et 1 chanson max
		private var songCpt:int = 0;
		private var imgCpt:int = 0;
		private var dropZoneSize:int;
		private var hardcoreLoader : URLStream;
		
		private var mp3Loaded : Boolean;
		private var jpgLoaded : Boolean;
		
		
		public function ExternalDragNDrop() 
		{
			addEventListener(Event.ADDED_TO_STAGE, init);
			
			//keyId = _keyId;
			dropZoneSize = GlobalParams.PAD_SIZE - 10;
			
			//mouseChildren 	= false;
		}
		
		private function init(e:Event):void 
		{
			removeEventListener(Event.ADDED_TO_STAGE, init);
			addEventListener(NativeDragEvent.NATIVE_DRAG_OVER, dragOver);
			addEventListener(NativeDragEvent.NATIVE_DRAG_COMPLETE, dragComplete);
			addEventListener(NativeDragEvent.NATIVE_DRAG_DROP, dragDrop);
			addEventListener(NativeDragEvent.NATIVE_DRAG_ENTER, dragEnter);
			addEventListener(NativeDragEvent.NATIVE_DRAG_EXIT, dragExit);
			addEventListener(NativeDragEvent.NATIVE_DRAG_START, dragStart);
			addEventListener(NativeDragEvent.NATIVE_DRAG_UPDATE, dragUpdate);
		}
		
		private function dragUpdate(e:NativeDragEvent):void 
		{
		}
		
		private function dragStart(e:NativeDragEvent):void 
		{
		}
		
		/**
		 * Fausse alerte sortie de la zone
		 */ 
		private function dragExit(e:NativeDragEvent):void 
		{
			dispatchEvent(new OutDragInEvent(OutDragInEvent.DRAG_OUT));
		}
		
		/**
		 * Entrée dans la zone
		 * @param	e
		 */
		private function dragEnter(e:NativeDragEvent):void 
		{
			dispatchEvent(new OutDragInEvent(OutDragInEvent.DRAG_OVER));
			NativeDragManager.acceptDragDrop(this);
		}
		
		/**
		 * Laché déposé
		 * @TODO gestion de l'encodage de fichier WAV
		 * @param	e
		 */
		private function dragDrop(e:NativeDragEvent):void 
		{
			NativeDragManager.dropAction = NativeDragActions.COPY;
			dispatchEvent(new OutDragInEvent(OutDragInEvent.DRAG_OUT));
			
			var clipBoard:Clipboard = Clipboard(e.clipboard);
			var dropFiles:Array = clipBoard.getData(ClipboardFormats.FILE_LIST_FORMAT) as Array;
			
			for each(var file:File in dropFiles) {
				var sourceFile:File = new File();
				
				switch(file.extension.toLowerCase() ) {
					case "mp3":
						sourceFile = sourceFile.resolvePath(file.nativePath);
						songCpt++;
						sm.copySongFile = sourceFile;
						if (_track.thumb != "")		completePad = true;
						if (_track.file != "") {
							needOverride = true;
							completePad = false;
						}
					break;
					case "wav":
						sourceFile = sourceFile.resolvePath(file.nativePath);
						songCpt++;
						sm.wavToMp3Encode = sourceFile;
						if (_track.thumb != "") completePad = true;
						if (_track.file != "") {
							needOverride = true;
							completePad = false;
						}
					break;
					
					case "jpg":
					case "jpeg":
					case "png":
						sourceFile = sourceFile.resolvePath(file.nativePath);
						imgCpt++;
						sm.copyImgFile = sourceFile;
						if (_track.file != "") completePad = true;
						if (_track.thumb != "") {
							needOverride = true;
							completePad = false;
						}
					break;
					case "bmp":
						sourceFile = sourceFile.resolvePath(file.nativePath);
						imgCpt++;
						sm.bmpToJpgEncode = sourceFile;
						if (_track.file != "") completePad = true;
						if (_track.thumb != "") {
							needOverride = true;
							completePad = false;
						}
					break;
					case "gif":
						sourceFile = sourceFile.resolvePath(file.nativePath);
						imgCpt++;
						sm.gifToPngEncode = sourceFile;
						if (_track.file != "") completePad = true;
						if (_track.thumb != "") {
							needOverride = true;
							completePad = false;
						}
					break;
					case "zip":
						
						if ( Capabilities.os.search("Mac") >= 0 )
						{
							hardcoreLoader = new URLStream();
							hardcoreLoader.addEventListener(Event.COMPLETE, hardcoreFileLoaded);
							hardcoreLoader.load( new URLRequest( file.url));
						}
					
						return;
					
					break;
					case "hardcore":
											
						hardcoreLoader = new URLStream();
						hardcoreLoader.addEventListener(Event.COMPLETE, hardcoreFileLoaded);
						hardcoreLoader.load( new URLRequest( file.url));
						
						return;
					break;
					default:
						/*	F A I L */
						badExtensionGesture();
						return;
					break;
				}
			}
			
			
			// check
			if (imgCpt > 1 || songCpt > 1)
				tooMuchFile();
			else
				proceed();
			
		}

		/* Proceed */
		private function proceed( _setByHardcore : Boolean = false ):void
		{
			sm.addEventListener(SaveManagerEvent.SAVE_PROCESS_SUCCEED, handleSaveProcessComplete);
			sm.addEventListener(SaveManagerEvent.SAVE_PROCESS_FAILED, handleSaveProcessFailed);
			sm.proceedDaSave(_track, _setByHardcore);
		}
		
		/**
		 * Précise que la sauvegarde à échoué
		 * @param	e
		 */
		private function handleSaveProcessFailed(e:SaveManagerEvent):void 
		{
			sm.removeEventListener(SaveManagerEvent.SAVE_PROCESS_SUCCEED, handleSaveProcessComplete);
			sm.removeEventListener(SaveManagerEvent.SAVE_PROCESS_FAILED, handleSaveProcessFailed);
			
			trace("### Echec de la sauvegarde " + e.data);
			flush();
		}
		
		/**
		 * Précise que la sauvegarde c'est effectué avec succès
		 * @param	e
		 */
		private function handleSaveProcessComplete(e:SaveManagerEvent):void 
		{
			sm.removeEventListener(SaveManagerEvent.SAVE_PROCESS_SUCCEED, handleSaveProcessComplete);
			sm.removeEventListener(SaveManagerEvent.SAVE_PROCESS_FAILED, handleSaveProcessFailed);
			
			_track = sm.track;
			
			if (!needOverride && !completePad)	dispatchEvent(new SaveManagerEvent(SaveManagerEvent.REFRESH_PADSMANAGER, [""+_track.keyId], true));
			
			flush();
		}
		
		/**
		 * Annulation de l'action, affichage de l'erreur
		 */
		private function tooMuchFile():void
		{
			flush();
			trace("####T O O   M U C H   F I L E####");
		}

		
		/* Hardcore Extension Handler */
		private function hardcoreFileLoaded( evt : Event ) : void
		{	
			hardcoreLoader.removeEventListener(Event.COMPLETE, hardcoreFileLoaded);
			
			var zipFile:ZipFile = new ZipFile(hardcoreLoader);
			
			for (var i:int = 0; i < zipFile.entries.length; i++)
			{
				var entry:ZipEntry = zipFile.entries[i];
				//trace("###"+entry.name);
				// extract the entry's data from the zip
				var data:ByteArray = zipFile.getInput(entry);
				
				
				/* JPG */
				if ( entry.name.search("jpg") > 0 )
				{
					trace("### JPG");
					var picture : File =  new File( SaveManager.URL_PATH_THUMB + "/" + entry.name );
					
					var fs : FileStream = new FileStream();
					fs.open( picture, FileMode.WRITE);
					fs.writeBytes( data );
					fs.close();
					
					_track.thumb = entry.name;
					
					imgCpt++;
					sm.copyImgFile = picture;
					
					if (_track.file != "") completePad = true;
					if (_track.thumb != "") {
						needOverride = true;
						completePad = false;
					}
					
					jpgLoaded = true;
				}
				
				/* MP3 */
				if ( entry.name.search("mp3") > 0 )
				{
					trace("### MP3");
					var sound : File =  new File( SaveManager.URL_PATH_MP3 + "/" + entry.name );
					
					var mfs: FileStream = new FileStream();
					mfs.open( sound, FileMode.WRITE);
					mfs.writeBytes( data );
					mfs.close();
					
					_track.file = entry.name;
					
					songCpt++;
					sm.copySongFile = sound;
					
					if (_track.thumb != "")		completePad = true;
					if (_track.file != "") {
						needOverride = true;
						completePad = false;
					}
					
					mp3Loaded = true;
					
				}
				
				//trace("---> " + jpgLoaded + " :: " + mp3Loaded);
				if(jpgLoaded && mp3Loaded) proceed(true);
			}
		}
		
		
		/**
		 * Anulation de l'action suite à une extension inconnue, affichage de l'erreur
		 */
		private function badExtensionGesture():void
		{
			trace("L'un des fichiers possède une extension inconnue");
			flush();
		}
		
		private function flush():void
		{
			needOverride = false;
			imgCpt = 0;
			songCpt = 0;
			sm.flush();
		}
		
		private function dragComplete(e:NativeDragEvent):void 
		{
		}
		
		private function dragOver(e:NativeDragEvent):void 
		{
		}
		
		public function set track(value:Track):void 
		{
			_track = value;
			_keyId = _track.keyId;
			if( !streamable ) sm = new SaveManager(_keyId);
		}
		
	}

}